package com.ruyuan.commodity.common.mamager.impl;

import cn.hutool.json.JSONUtil;
import com.ruyuan.commodity.common.mamager.*;
import com.ruyuan.commodity.enums.GoodsMarketEnableEnums;
import com.ruyuan.commodity.enums.RedisCacheKey;
import com.ruyuan.commodity.enums.RedissonLockEnums;
import com.ruyuan.commodity.exception.ResourceNotFoundException;
import com.ruyuan.commodity.model.goods.dos.CategoryDO;
import com.ruyuan.commodity.model.goods.dos.GoodsDO;
import com.ruyuan.commodity.model.goods.dos.GoodsGalleryDO;
import com.ruyuan.commodity.model.goods.vo.GoodsDetail;
import com.ruyuan.commodity.model.goods.vo.GoodsParamsGroupVO;
import org.redisson.api.RLock;
import org.redisson.api.RedissonClient;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.util.ObjectUtils;
import org.springframework.util.StringUtils;

import java.util.List;

/**
 * 商品详情实现类
 **/
@Service
public class GoodsDetailManagerImpl implements GoodsDetailManager {

    private static final org.slf4j.Logger LOG = org.slf4j.LoggerFactory.getLogger(GoodsDetailManagerImpl.class);

    /**
     * 商品信息查询管理器
     */
    @Autowired
    private GoodsInfoQueryManager goodsInfoQueryManager;
    /**
     * 商品属性管理器
     */
    @Autowired
    private GoodsParamsManager goodsParamsManager;
    /**
     * 商品分类管理器
     */
    @Autowired
    private CategoryManager categoryManager;
    /**
     * 商品相册管理器
     */
    @Autowired
    private GoodsInfoGalleryManager goodsInfoGalleryManager;
    /**
     * redisson客户端
     */
    @Autowired
    private RedissonClient redissonClient;
    /**
     * redis操作模板
     */
    @Autowired
    private RedisTemplate<String, String> redisTemplate;

    /**
     * 获取商品详情
     *
     * @param goodsId 商品id
     * @return 商品详情
     */
    @Override
    public GoodsDetail getGoodsDetail(Long goodsId) {
        String lockKey = RedissonLockEnums.GOODS_DETAIL_LOCK_PREFIX.getKey() + goodsId;
        RLock lock = redissonClient.getLock(lockKey);
        lock.lock();
        GoodsDetail goodsDetail = null;
        try {
            String key = RedisCacheKey.GOODS_DETAIL_KEY_PREFIX.getPrefix() + goodsId;
            String goodsDetailStr = redisTemplate.opsForValue().get(key);

            // 不为空走缓存逻辑
            if (!StringUtils.isEmpty(goodsDetailStr)) {
                LOG.info("进入商品详情缓存逻辑");
                goodsDetail = JSONUtil.toBean(goodsDetailStr, GoodsDetail.class);
                return goodsDetail;
            }

            // 为空从DB中查询 回种缓存
            if (StringUtils.isEmpty(goodsDetailStr)) {
                LOG.info("进入商品详情DB逻辑");
                GoodsDO goods = goodsInfoQueryManager.getModel(goodsId);
                if (goods == null) {
                    throw new ResourceNotFoundException("不存在此商品");
                }
                goodsDetail = new GoodsDetail();
                BeanUtils.copyProperties(goods, goodsDetail);
                int goodsOff = GoodsMarketEnableEnums.MARKET_ENABLE_DOWN.getCode();
                // 商品不存在，直接返回
                if (ObjectUtils.isEmpty(goods)) {
                    goodsDetail.setGoodsOff(goodsOff);
                    return goodsDetail;
                }
                // 分类
                CategoryDO category = categoryManager.getModel(goods.getCategoryId());
                goodsDetail.setCategoryName(category == null ? "" : category.getName());
                // 上架状态
                if (GoodsMarketEnableEnums.MARKET_ENABLE_UP.getCode().equals(goods.getMarketEnable())) {
                    goodsOff = GoodsMarketEnableEnums.MARKET_ENABLE_UP.getCode();
                }
                goodsDetail.setGoodsOff(goodsOff);
                // 参数
                List<GoodsParamsGroupVO> list = goodsParamsManager.queryGoodsParams(goods.getCategoryId(), goodsId);
                goodsDetail.setParamList(list);
                // 相册
                List<GoodsGalleryDO> galleryList = goodsInfoGalleryManager.list(goodsId);
                goodsDetail.setGalleryList(galleryList);
                // 商品好平率
                goodsDetail.setGrade(goodsInfoQueryManager.getGoodsGrade(goodsId));
                // 查询到后回种缓存
                redisTemplate.opsForValue().set(key, JSONUtil.toJsonStr(goodsDetail));
            }


            return goodsDetail;
        } finally {
            lock.unlock();
        }
    }
}
